﻿using System;
using System.IO;
using System.Xml;
using System.Configuration;
using System.Web;
using SyCODE.Component.DataFactory;
using System.Collections.Specialized;
using System.Data.Common;
using System.Text.RegularExpressions;

/// <summary>
/// SyCODE 的摘要说明
/// </summary>
namespace SyCODE.Blog
{
    /// <summary>
    /// RSS 输出
    /// </summary>
    public class Rss : IHttpHandler
    {
        /// <summary>
        /// 获取当前访问的完整域名
        /// </summary>
        /// <param name="uri">当前访问的统一资源标示符</param>
        /// <returns></returns>
        private string GetDomain(Uri uri)
        {
            return uri.AbsoluteUri.Substring(0, uri.AbsoluteUri.Length - uri.PathAndQuery.Length + 1);
        }

        public bool IsReusable
        {
            get { return true; }
        }

        public void ProcessRequest(HttpContext context)
        {
            if (!context.Request.QueryString.HasKeys())
            {
                return;
            }

            string host = GetDomain(context.Request.Url);

            context.Response.ContentType = "text/xml";

            XmlTextWriter writer = new XmlTextWriter(context.Response.OutputStream, context.Response.ContentEncoding);
            writer.WriteStartDocument();
            writer.WriteStartElement("rss");
            writer.WriteAttributeString("version", "2.0");
            writer.WriteAttributeString("xmlns:slash", "http://purl.org/rss/1.0/modules/slash/");
            writer.WriteAttributeString("xmlns:dcterms", "http://purl.org/dc/terms/");

            DBAM dbam = new DBAM();
            dbam.BuildParameters("rss", context.Request.QueryString);
            try
            {
                DbDataReader dr = dbam.ExecuteReader();
                writer.WriteStartElement("channel");
                if (dr.Read())
                {
                    string bloger = context.Request.QueryString["u"];
                    string link = host + bloger;

                    writer.WriteStartElement("title");
                    writer.WriteCData(dr.GetString(0));
                    writer.WriteEndElement(/*title*/);

                    writer.WriteStartElement("link");
                    writer.WriteString(link);
                    writer.WriteEndElement(/*link*/);

                    writer.WriteStartElement("description");
                    writer.WriteCData(dr.GetString(1));
                    writer.WriteEndElement(/*description*/);

                    writer.WriteStartElement("language");
                    writer.WriteString("zh-CN");
                    writer.WriteEndElement(/*language*/);

                    writer.WriteStartElement("pubDate");
                    writer.WriteString(DateTime.Now.Date.ToString("r"));
                    writer.WriteEndElement(/*pubDate*/);

                    writer.WriteStartElement("lastBuildDate");
                    writer.WriteString(DateTime.Now.Date.ToString("r"));
                    writer.WriteEndElement(/*lastBuildDate*/);

                    writer.WriteStartElement("docs");
                    writer.WriteString("http://blogs.law.harvard.edu/tech/rss");
                    writer.WriteEndElement(/*docs*/);

                    writer.WriteStartElement("generator");
                    writer.WriteString("sy-blog generator");
                    writer.WriteEndElement(/*generator*/);

                    writer.WriteStartElement("ttl");
                    writer.WriteString("120");
                    writer.WriteEndElement(/*ttl*/);

                    writer.WriteStartElement("image");

                    writer.WriteStartElement("title");
                    writer.WriteCData(dr.GetString(0));
                    writer.WriteEndElement(/*title*/);

                    writer.WriteStartElement("url");
                    writer.WriteString(host + dr.GetString(2).TrimStart('/'));
                    writer.WriteEndElement(/*url*/);

                    writer.WriteStartElement("link");
                    writer.WriteString(link);
                    writer.WriteEndElement(/*link*/);

                    writer.WriteEndElement(/*image*/);

                    if (dr.NextResult())
                    {
                        while (dr.Read())
                        {
                            writer.WriteStartElement("item");

                            writer.WriteStartElement("title");
                            writer.WriteCData(dr.GetString(0));
                            writer.WriteEndElement(/*title*/);

                            writer.WriteStartElement("link");
                            writer.WriteString(link + "/topic/" + dr.GetInt64(1).ToString());
                            writer.WriteEndElement(/*link*/);

                            writer.WriteStartElement("description");
                            writer.WriteCData(Regex.Replace(Regex.Replace(Regex.Replace(dr.GetString(2), @"\n", "<br/>", RegexOptions.IgnoreCase), @"\s", "&nbsp;"), @"\[img\]([^\[]*)\[/img\]", 
                                delegate(Match m)
                                {
                                    return "<img src=\"" + m.Groups[1].Value.Replace("&nbsp;", "%20") + "\" />";
                                }));
                            writer.WriteEndElement(/*description*/);

                            writer.WriteStartElement("author");
                            writer.WriteString(bloger);
                            writer.WriteEndElement(/*author*/);

                            writer.WriteStartElement("slash:comments");
                            writer.WriteString(dr.GetInt32(3).ToString());
                            writer.WriteEndElement(/*slash:comments*/);

                            writer.WriteStartElement("pubDate");
                            writer.WriteString(dr.GetDateTime(4).ToString("r"));
                            writer.WriteEndElement(/*pubDate*/);

                            writer.WriteStartElement("dcterms:modified");
                            writer.WriteString(dr.GetDateTime(4).ToString("r"));
                            writer.WriteEndElement(/*dcterms:modified*/);

                            writer.WriteEndElement(/*item*/);
                        }
                    }
                }

                writer.WriteEndElement(/*channel*/);
            }
            finally
            {
                dbam.Dispose();
            }

            writer.WriteEndElement(/*rss*/);
            writer.WriteEndDocument();

            writer.Flush();
        }
    }
}